package com.ruoyi.generator.service.impl;

import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.generator.domain.FromBuildConfig;
import com.ruoyi.generator.domain.FromBuildOptionsConfig;
import com.ruoyi.generator.domain.FromBuildRuleConfig;
import com.ruoyi.generator.domain.GenTableColumn;
import com.ruoyi.generator.mapper.FromBuildConfigMapper;
import com.ruoyi.generator.mapper.FromBuildOptionsConfigMapper;
import com.ruoyi.generator.mapper.FromBuildRuleConfigMapper;
import com.ruoyi.generator.mapper.GenTableColumnMapper;
import com.ruoyi.generator.service.IFromBuildConfigService;
import com.ruoyi.generator.service.IGenTableService;
import com.ruoyi.generator.util.GenUtils;
import com.ruoyi.generator.util.ModuleReqPrefixUtil;
import com.ruoyi.system.service.ISysDictTypeService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.lang.reflect.Array;
import java.util.Arrays;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * 单设计_配置Service业务层处理
 *
 * @author XL
 * @date 2022-08-05 12:01:23
 */
@Service
public class FromBuildConfigServiceImpl implements IFromBuildConfigService {
    @Autowired
    private FromBuildConfigMapper fromBuildConfigMapper;

    /**
     * 删除校验规则
     */
    @Autowired
    private FromBuildRuleConfigMapper fromBuildRuleConfigMapper;

    /**
     * 删除下拉选项
     */
    @Autowired
    private FromBuildOptionsConfigMapper fromBuildOptionsConfigMapper;

    @Autowired
    private GenTableColumnMapper genTableColumnMapper;

    @Autowired
    private IGenTableService iGenTableService;

    @Autowired
    private ISysDictTypeService dictTypeService;

    /**
     * 查询单设计_配置
     *
     * @param id 单设计_配置ID
     * @return 单设计_配置
     */
    @Override
    public FromBuildConfig selectFromBuildConfigById(Long id) {
        return fromBuildConfigMapper.selectFromBuildConfigById(id);
    }

    /**
     * 查询单设计_配置列表
     *
     * @param fromBuildConfig 单设计_配置
     * @return 单设计_配置
     */
    @Override
    public List<FromBuildConfig> selectFromBuildConfigList(FromBuildConfig fromBuildConfig) {
        return fromBuildConfigMapper.selectFromBuildConfigList(fromBuildConfig);
    }

    /**
     * 新增单设计_配置
     *
     * @param fromBuildConfig 单设计_配置
     * @return 结果
     */
    @Override
    public int insertFromBuildConfig(FromBuildConfig fromBuildConfig) {
        return fromBuildConfigMapper.insertFromBuildConfig(fromBuildConfig);
    }

    /**
     * 修改单设计_配置
     *
     * @param fromBuildConfig 单设计_配置
     * @return 结果
     */
    @Override
    public int updateFromBuildConfig(FromBuildConfig fromBuildConfig) {
        return fromBuildConfigMapper.updateFromBuildConfig(fromBuildConfig);
    }

    /**
     * 批量删除单设计_配置
     *
     * @param ids 需要删除的单设计_配置ID
     * @return 结果
     */
    @Override
    public int deleteFromBuildConfigByIds(Long[] ids) {
        return fromBuildConfigMapper.deleteFromBuildConfigByIds(ids);
    }

    /**
     * 删除单设计_配置信息
     *
     * @param id 单设计_配置ID
     * @return 结果
     */
    @Override
    public int deleteFromBuildConfigById(Long id) {
        return fromBuildConfigMapper.deleteFromBuildConfigById(id);
    }

    /**
     * ==================================================================================================
     */

    /**
     * 获取表单设计字段配置信息
     */
    @Override
    public List<FromBuildConfig> getFormBuildConfig(String formBuildKey, String clientType) {

        List<FromBuildConfig> formBuildConfigs = fromBuildConfigMapper.getFormBuildConfig(formBuildKey, clientType);
        try{
            for(FromBuildConfig item:formBuildConfigs){
                if(StringUtils.isNotEmptyIncludeNull(item.getAutosizeObj())){
                    item.setAutosize(JSONObject.parseObject(item.getAutosizeObj()));
                }
            }
        }catch (Exception e){ }

        return formBuildConfigs;
    }

    public List<Map<String, String>> getTableGenInfo(String formBuildKey) {

        return fromBuildConfigMapper.getTableGenInfo(formBuildKey);
    }

    /**
     * 特殊参数处理
     */
    public List<Map<String, Object>> paramDeal(List<FromBuildConfig> formBuildConfigInfoList) {

        try{
            for(FromBuildConfig item:formBuildConfigInfoList){
                if(StringUtils.isNotEmptyIncludeNull(item.getAutosizeObj())){
                    item.setAutosize(JSONObject.parseObject(item.getAutosizeObj()));
                }
            }
        }catch (Exception e){ }

        String s = JSONObject.toJSONString(formBuildConfigInfoList);
        s = s.replaceAll("prefixIcon", "prefix-icon")
                .replaceAll("\"VModel\"", "\"vModel\"")
                .replaceAll("suffixIcon", "suffix-icon")
                .replaceAll("showWordLimit", "show-word-limit")
                .replaceAll("activeValue", "active-value")
                .replaceAll("inactiveValue", "inactive-value");

        List result = JSONObject.parseObject(s, List.class);

        return result;
    }

    /**
     * 特殊参数处理
     */
    private void paramDeal(JSONObject obj) throws Exception {
        obj.put("prefixIcon", obj.get("prefix-icon"));
        obj.remove("prefix-icon");
        obj.put("suffixIcon", obj.get("suffix-icon"));
        obj.remove("suffix-icon");
        obj.put("showWordLimit", obj.get("show-word-limit"));
        obj.remove("show-word-limit");
        obj.put("activeValue", obj.get("active-value"));
        obj.remove("active-value");
        obj.put("inactiveValue", obj.get("inactive-value"));
        obj.remove("inactive-value");
        /**
         * 样式
         */
        obj.remove("style");
        /**
         * 校验规则
         */
        obj.remove("regList");
        /**
         * 子组件
         */
        obj.remove("children");
    }

    /**
     * 处理流程节点信息
     */
    @Transactional(rollbackFor = Exception.class)
    public AjaxResult saveFormInfo(Long tableId,String formBuildKey, String clientType, List<FromBuildConfig> fromBuildConfigs) throws Exception {

        if (StringUtils.isEmpty(formBuildKey)) {
            return AjaxResult.error("表单设计编码不能为空");
        }
        /**
         * 删除校验规则
         */
        fromBuildRuleConfigMapper.deleteFormRuleConfigByBuildKey(formBuildKey, clientType);
        /**
         * 删除下拉选项
         */
        fromBuildOptionsConfigMapper.deleteFromBuildOptionsConfigByBuildKey(formBuildKey, clientType);
        /**
         * 删除表单配置
         */
        fromBuildConfigMapper.deleteFromBuildConfigByBuildKey(formBuildKey, clientType);

        if(fromBuildConfigs==null){
            return AjaxResult.success();
        }

        for (int i = 0; i < fromBuildConfigs.size(); i++) {
            FromBuildConfig fromBuildConfig = fromBuildConfigs.get(i);
            /**
             * 显示顺序
             */
            fromBuildConfig.setSort(i + 1);
            /**
             * 显示层级
             */
            fromBuildConfig.setGrade(1);
            /**
             * 终端类型__PC_Mobile
             */
            fromBuildConfig.setClientType(clientType);
            /**
             * 处理表单信息
             */
            this.dealFormItem(tableId,formBuildKey, null, fromBuildConfig);
        }

        return AjaxResult.success();
    }

    /**
     * 特殊参数处理
     */
    private void dealFormItem(Long tableId,String formBuildKey, FromBuildConfig parent, FromBuildConfig fromBuildConfig) throws Exception {
        /**
         * 校验规则
         */
        List<FromBuildRuleConfig> regList = fromBuildConfig.getRegList();
        /**
         * 选项值
         */
        List<FromBuildOptionsConfig> options = fromBuildConfig.getOptions();
        /**
         * 子组件
         */
        List<FromBuildConfig> children = fromBuildConfig.getChildren();

        /**
         * 特殊参数处理
         */
//        this.paramDeal(obj);

        fromBuildConfig.setStyle(String.valueOf(fromBuildConfig.getStyle()));
        /**
         * 设置流程编码
         */
        fromBuildConfig.setBuildKey(formBuildKey);
        /**
         * 设置表单组件UUID
         */
        fromBuildConfig.setFormUuid(GenUtils.getUUID());
        fromBuildConfig.setFormId(fromBuildConfig.getFormUuid());
        /**
         * 将父组件的一些属性同步更新到子组件
         */
        if (parent != null) {
            /**
             * 设置表单父组件UUID
             */
            fromBuildConfig.setParentFormUuid(parent.getFormUuid());
            /**
             * 如果父组件设置根据其他组件的值判断是否显示，当子组件未设置时同时修改子组件
             */
            if (StringUtils.isEmpty(fromBuildConfig.getMeetShowVModel())) {
                fromBuildConfig.setMeetShowVModel(parent.getMeetShowVModel());
            }
            if (StringUtils.isEmpty(fromBuildConfig.getMeetShowVModelVal())) {
                fromBuildConfig.setMeetShowVModelVal(parent.getMeetShowVModelVal());
            }
        }
        /**
         * 判断是否存在子组件
         */
        fromBuildConfig.setHasChildren("0");
        if (children != null && children.size() >= 0) {
            fromBuildConfig.setHasChildren("1");
            this.dealFormItemChild(tableId,formBuildKey, fromBuildConfig, children);
        }
        /**
         * 处理校验规则
         */
        if (regList != null && regList.size() > 0) {
            for (int i = 0; i < regList.size(); i++) {
                FromBuildRuleConfig fromBuildRuleConfig = regList.get(i);
                /**
                 * 设置流程节点编码
                 */
                fromBuildRuleConfig.setBuildKey(formBuildKey);
                fromBuildRuleConfig.setFormUuid(fromBuildConfig.getFormUuid());
                fromBuildRuleConfig.setSort(i + 1);
                fromBuildRuleConfig.setClientType(fromBuildConfig.getClientType());
                fromBuildRuleConfigMapper.insertFromBuildRuleConfig(fromBuildRuleConfig);
            }
        }
        /**
         * 处理选项值
         */
        if (StringUtils.isEmpty(fromBuildConfig.getOptionDictCode()) && options != null && options.size() > 0) {
            for (int i = 0; i < options.size(); i++) {
                FromBuildOptionsConfig fromBuildOptionsConfig = options.get(i);
                /**
                 * 设置流程节点编码
                 */
                fromBuildOptionsConfig.setBuildKey(formBuildKey);
                fromBuildOptionsConfig.setFormUuid(fromBuildConfig.getFormUuid());
                fromBuildOptionsConfig.setSort(i + 1);
                fromBuildOptionsConfig.setClientType(fromBuildConfig.getClientType());
                fromBuildOptionsConfigMapper.insertFromBuildOptionsConfig(fromBuildOptionsConfig);
            }
        }
        /**
         * 判断当前组件是否是子表，如果是子表则需要获取出对应全类名
         */
        if (StringUtils.isNotEmpty(fromBuildConfig.getModuleType()) && "ChildTable".equals(fromBuildConfig.getModuleType())) {
            List<Map<String, String>> tableGenInfo = fromBuildConfigMapper.getTableGenInfo(fromBuildConfig.getVModel());
            if (tableGenInfo.size() > 0) {
                //服务实现全类名
                fromBuildConfig.setServiceName(StringUtils.format("{}.service.impl.{}ServiceImpl", tableGenInfo.get(0).get("packageName"), tableGenInfo.get(0).get("businessName")));
                //子表接口请求前缀
                fromBuildConfig.setPrefixUrl(StringUtils.format("/{}/{}", ModuleReqPrefixUtil.getModuleRequestPrefix(tableGenInfo.get(0).get("moduleName")), tableGenInfo.get(0).get("businessName")));
            }
        }
        Object defaultValue = fromBuildConfig.getDefaultValue();
        if(defaultValue instanceof List){
            List defaultValues= (List) defaultValue;
            fromBuildConfig.setDefaultValue(String.join(",", defaultValues));
        }
        /**
         * 保存表单配置信息
         */
        fromBuildConfigMapper.insertFromBuildConfig(fromBuildConfig);
        /**
         * 修改对应字段配置信息
         */
        genTableColumnMapper.updateGenTableColumnByJavaField(genNeedUpdateTableColumnInfo(tableId,fromBuildConfig));
    }

    /**
     * 特殊参数处理
     */
    private void dealFormItemChild(Long tableId,String formBuildKey, FromBuildConfig parent, List<FromBuildConfig> children) throws Exception {

        for (int i = 0; i < children.size(); i++) {
            FromBuildConfig fromBuildConfig = children.get(i);
            /**
             * 显示顺序
             */
            fromBuildConfig.setSort(i + 1);
            /**
             * 显示层级
             */
            fromBuildConfig.setGrade(2);
            /**
             * 终端类型__PC_Mobile
             */
            fromBuildConfig.setClientType(parent.getClientType());

            this.dealFormItem(tableId,formBuildKey, parent, fromBuildConfig);

        }
    }

    /**
     * 获取需要修改的字段信息
     * @param fromBuildConfig
     * @return
     */
    private GenTableColumn genNeedUpdateTableColumnInfo(Long tableId,FromBuildConfig fromBuildConfig){
        GenTableColumn genTableColumn=new GenTableColumn();
        /** 归属表编号 */
        genTableColumn.setTableId(tableId);
        /** JAVA字段名 */
        genTableColumn.setJavaField(fromBuildConfig.getVModel());
        /** 中文字段名 */
        genTableColumn.setColumnComment(fromBuildConfig.getLabel());
//        /** 是否列表字段（1是） */
//        genTableColumn.setIsList(getGenTableColumnBoolStr(fromBuildConfig.getIsListShow()));
//        /** 列表宽度 */
//        if(StringUtils.isNotEmptyIncludeNull(fromBuildConfig.getListColumnWidth())){
//            genTableColumn.setColumnWidth(Integer.parseInt(fromBuildConfig.getListColumnWidth()));
//        }
//        /** 列表对齐方式 */
//        genTableColumn.setColumnAlign(fromBuildConfig.getListColumnAlign());
//        /** 是否查询字段（1是） */
//        genTableColumn.setIsQuery(getGenTableColumnBoolStr(fromBuildConfig.getIsQuery()));
//        /** 查询方式（EQ等于、NE不等于、GT大于、LT小于、LIKE模糊、BETWEEN范围） */
//        genTableColumn.setQueryType(fromBuildConfig.getQueryType());
        /** 字典类型 */
        genTableColumn.setDictType(fromBuildConfig.getOptionDictCode());
        /** 搜索表名__针对搜索文本框时的配置 **/
        genTableColumn.setSearchModel(fromBuildConfig.getSearchModel());

        return genTableColumn;
    }

    /**
     * 转换成gen_table_column表中的bool表达
     * @param bool
     * @return
     */
    private String getGenTableColumnBoolStr(String bool){
        if(StringUtils.isEmptyIncludeNull(bool)){
            return "0";
        }
        return "true".equals(bool.toLowerCase())?"1":"0";
    }

    /**
     * 根据表名获取对应字段配置信息
     * @param tabName
     * @return
     */
    @Override
    public AjaxResult getColumnConfigByTableName(String tabName){
        try {
            List<Map<String, Object>> fieldInfo = iGenTableService.getFieldByTabName(tabName);
            for (Map<String, Object> columnConfig : fieldInfo) {
                if (StringUtils.isNotEmpty(String.valueOf(columnConfig.get("dictType")))
                        && Arrays.asList("select","multipleSelect","allowCreateSelect","multipleallowCreateSelect").contains(columnConfig.get("htmlType"))) {
                    String dictType = columnConfig.get("dictType").toString();
                    columnConfig.put("dictItems", dictTypeService.selectDictDataByType(dictType));
                }
                /**
                 * 处理字段类型
                 */
                String columnType = String.valueOf(columnConfig.get("columnType"));
                //字段长度
                columnConfig.put("columnLength",getColumnLength(columnType));
            }
            return AjaxResult.success(fieldInfo);
        } catch (Exception e) {
            return AjaxResult.error("获取异常");
        }
    }

    /**
     * 获取字段长度
     *
     * @param columnType 列类型
     * @return 截取后的列类型
     */
    private Integer getColumnLength(String columnType)
    {
        if (StringUtils.indexOf(columnType, "(") > 0)
        {
            String length = StringUtils.substringBetween(columnType, "(", ")");
            return Integer.valueOf(length);
        }
        else
        {
            return 0;
        }
    }
}
